﻿#pragma once

#include "Controller.h"

#include <boost/signal.hpp>
#include "../domain/models/CardsCollection.h"
#include "../domain/models/Player.h"
#include "../views/abstract/IAccusationView.h"

namespace Controllers {

	/**
	* Kontroler oskarżenia.
	* Pyta gracza, czy chce dokonać podejrzenia, czy wysunąć oskarżenie.
	* W przypadku wysuniecia oskarżenia pyta o karty w oskarżeniu i przekazuje je przez odpowiednie wydarzenie.
	*/
	class AccusationController: public Controller
	{
	protected:
		Views::IAccusationView* view;
		Cards::CardSet searched_cards;
		Players::Player* current_player;
		Cards::CardsCollection cards;

	public:
		boost::signal<void ()> accusationCorrectEvent; /**< Zdarzenie wywoływane przy poprawnym oskarżeniu */
		boost::signal<void ()> accusationIncorrectEvent; /**< Zdarzenie wywoływane przy niepoprawnym oskarżeniu */
		boost::signal<void ()> accusationNotPerformedEvent; /**< Zdarzenie wywoływane przy wybraniu wyprowadzenia podejrzenia */

		/**
		* Konstruktor kontrolera oskarżenia
		* @param view Widok oskarżenia
		* @param logger Logger
		* @param player Aktualny gracz, który wykonuje ruch
		* @param cards Kolekcja wszystkich kart w grze
		* @param searched_cards Poszukiwane karty
		*/
		AccusationController(Views::IAccusationView*, Utils::Logging::ILogger* logger, Players::Player*,
			Cards::CardsCollection, Cards::CardSet);
		~AccusationController();

		void perform(); /**< Dokonuje oskarżenia */

	protected:
		/**
		* Sprawdza czy karty podane przez użytkownika są takie same jak te ukryte.
		* @param picked_card Karty wybrane przez uzytkownika
		* @return Prawda, jeśli karty się zgadzają
		*/
		bool checkCards(Cards::CardSet& picked_cards);
		/**
		* Sprawdza czy podejrzenie jest poprawne.
		* @param picked_card Karty wybrane przez uzytkownika
		* @return Prawda, jeśli podejrzenie jest poprawne
		*/
		bool isAccusationCorrect(Cards::CardSet&);
		/**
		* Wywoływane po ustawieniu przez gracza decyzji, czy dokonać oskarżenia
		* @param decision Decyzja gracza (true - oskarżenie, false - podejrzenie)
		*/
		void onPlayerDecisionSet(bool decision);
		void onCardsInAccusationSet(Cards::CardSet); /**< Wywoływane po wybraniu przez gracza kart w oskarżeniu. */
	};
}

